/*
 * listas.h
 *
 *  Created on: 25-nov-2009
 *      Author: pablo
 */

#ifndef LISTAS_H_
#define LISTAS_H_

#include <sys/socket.h>
#include <pthread.h>
#include "constantes.h"
#include "consulta.h"
//#include "message.h"


/* mutex */
extern pthread_mutex_t mutexListaCache;
extern pthread_mutex_t mutexListaEnviar;
extern pthread_mutex_t mutexListaServidores;
extern pthread_mutex_t mutexListaEncontrados;
extern pthread_mutex_t mutexListaQuerys;

//definimos los tipos de lista
#define MENSAJE		1
#define QUERY		2
#define QUERY_ID	3
#define TRANSFER	4
#define SERVENT		5

//nodo de una lista
typedef struct nodo{
	char *key;
	void *datos;
	struct nodo *next;
} nodo;

//definicion de lista
typedef struct _lista{
	int tipo;
	unsigned int tam;
	struct nodo *inicio;
	struct nodo *fin;
	struct nodo *actual; //se puede usar un numero 'X' pero entonces recuperar el nodo implica X saltos
} lista;

lista listaCache;
lista listaEnviar;
lista listaServidores;
lista listaEncontrados;
lista listaQuerys;

// Estructura de nodos
struct serventNode{
	unsigned int socket_fd;
	struct sockaddr addr;
};

// Estructura de queries
struct queryId{
	unsigned char id[LENGTH_MESSAGE_ID];// identificador de mensaje
	unsigned int sock; 					// identificador de socket
};



// metodos
int newLista(int tipo, lista *l); //inicializa una lista
int insertLista( lista *l, char * key, void * dato );// inserta en la lista por el final
int resetLista( lista *l ); //vamos el inicio de la lista
struct nodo * nextLista( lista *l); //devuelve el nodo actual de la lista y pasa a apuntar al sig.
struct nodo * buscarNodo(char * key,  lista *l ); //dada una clave devuelve el nodo que coincide
struct nodo * primerNodo( lista *l ); //devuelve el primer nodo de la lista, y lo borra
int eliminarNodo(char * key,  lista *l ); //elimina el nodo con la clave pasada
int freeLista( lista *l ); //libera el espacio ocupado por la lista



int inicializarListas();
int freeListas();

// Metodos para la lista con los mensajes
int insertMessage(struct message *id);
struct message *extractMessage ();

// Lista de identificacion de Querys
int insertarQueryId (struct queryId *id);
struct queryId *buscarQueryId ( char *id );
int borrarQueryId (char *id);
int mostrarNodosQuerys ();

// Lista de servidores en cache
int insertNodoCache(struct serventNode *id );
struct serventNode * getNodoCache();
int borrarNodoCache ( unsigned int id );
int mostrarNodosCache ();

// Lista de servidores a los q estamos conectados
int insertNodeConectado(struct serventNode *id);
struct serventNode * getNodoConectado ();
int borrarNodoConectado (unsigned int id);
int mostrarNodosConectados ();
struct serventNode * firstNodoConectado();
struct serventNode * nextNodoConectado(struct serventNode *id );

/*
 * TIENE Q HABER UNA LISTA DE QUERYS, HAY Q CREAR LA ESTRUCTURA DE QUERYS y los metodos de la lista
*/
// Lista de los encontrados
int freeEncontrados();
int mostrarListaEncontrados ();
int insertEncontrado (struct fileQuery *id );
struct fileQuery * buscarEncontrado( int id );

#endif /* LISTAS_H_ */
